using System;
using System.Drawing;
using System.Drawing.Drawing2D;

namespace WebChart
{
	public class StackedAreaChart : Chart
	{
		// Methods
		public StackedAreaChart()
		{
		}

		public StackedAreaChart(ChartPointCollection data) : base(data)
		{
		}

		public StackedAreaChart(ChartPointCollection data, Color color) : base(data, color)
		{
		}

		public override void GetMinMaxMeanValue(out float min, out float max, out float mean)
		{
			ChartEngine engine = base.Engine;
			min = 0f;
			max = 0f;
			mean = 0f;
			int stackedCount = this.GetStackedCount(engine.Charts);
			if ((stackedCount > 0) && (engine.MaxPoints > 0))
			{
				Chart[] chartArray = new Chart[stackedCount];
				int num2 = 0;
				foreach (Chart chart in engine.Charts)
				{
					if (chart is StackedAreaChart)
					{
						chartArray[num2++] = chart;
					}
				}
				float num3 = 0f;
				min = 0f;
				max = float.MinValue;
				for (int i = 0; i < engine.MaxPoints; i++)
				{
					float num6 = 0f;
					float num7 = 0f;
					for (int j = 0; j < stackedCount; j++)
					{
						ChartPointCollection data = chartArray[j].Data;
						if (data.Count > i)
						{
							float yvalue = data[i].yvalue;
							if (yvalue >= 0f)
							{
								num6 += yvalue;
							}
							else
							{
								num7 += yvalue;
							}
						}
					}
					if (num7 < min)
					{
						min = num7;
					}
					if (num6 > max)
					{
						max = num6;
					}
					num3 += num6 + num7;
				}
				mean = num3 / ((float) engine.MaxPoints);
				if (base.dataLabels.visible)
				{
					float num9 = (max - min) / 10f;
					max += num9;
				}
			}
		}

		private int GetStackedCount(ChartCollection charts)
		{
			int num = 0;
			bool flag = true;
			foreach (Chart chart in charts)
			{
				if (!(chart is StackedAreaChart))
				{
					continue;
				}
				if (flag)
				{
					if (chart != this)
					{
						return 0;
					}
					flag = false;
				}
				num++;
			}
			return num;
		}

		public override void Render(Graphics graphics, int width, int height)
		{
			ChartEngine engine = base.Engine;
			int stackedCount = this.GetStackedCount(engine.Charts);
			if (stackedCount != 0)
			{
				float scaleX = engine.scaleX;
				float scaleY = engine.scaleY;
				float num5 = scaleX / 2f;
				StackedAreaChart[] chartArray = new StackedAreaChart[stackedCount];
				Pen[] penArray = new Pen[stackedCount];
				Brush[] brushArray = new Brush[stackedCount];
				Point[] pointArray = new Point[stackedCount];
				GraphicsPath[] pathArray = new GraphicsPath[stackedCount];
				bool flag = (base.shadow != null) && base.Shadow.Visible;
				Brush brush = null;
				GraphicsPath[] pathArray2 = null;
				if (flag)
				{
					pathArray2 = new GraphicsPath[stackedCount];
					brush = new SolidBrush(base.Shadow.Color);
				}
				int index = 0;
				foreach (Chart chart in engine.Charts)
				{
					chartArray[index] = chart as StackedAreaChart;
					if (chartArray[index] != null)
					{
						penArray[index] = chart.Line.GetPen(graphics);
						brushArray[index] = chart.Fill.GetBrush(graphics);
						pointArray[index] = new Point((int) num5, 0);
						pathArray[index] = new GraphicsPath();
						if (flag)
						{
							pathArray2[index] = new GraphicsPath();
						}
						index++;
						if (index >= stackedCount)
						{
							break;
						}
					}
				}
				for (int i = 0; i < engine.MaxPoints; i++)
				{
					float num8 = 0f;
					float num9 = 0f;
					for (int j = 0; j < stackedCount; j++)
					{
						ChartPointCollection data = chartArray[j].Data;
						if (data.Count > i)
						{
							float num13;
							float num14;
							float yvalue = data[i].yvalue;
							float num11 = i * scaleX;
							float num12 = scaleX - 1f;
							if (yvalue > 0f)
							{
								num8 += yvalue;
								num13 = num8 * scaleY;
								num14 = -yvalue * scaleY;
								Point point = new Point((int) (num11 + num5), (int) num13);
								pathArray[j].AddLine(pointArray[j], point);
								if (flag)
								{
									pathArray2[j].AddLine((int) (pointArray[j].X + base.shadow.OffsetX), (int) (pointArray[j].Y + base.shadow.OffsetY), (int) (point.X + base.shadow.OffsetX), (int) (point.Y + base.shadow.OffsetY));
								}
								pointArray[j] = point;
							}
							else if (yvalue < 0f)
							{
								num13 = num9 * scaleY;
								num14 = yvalue * scaleY;
								num9 += yvalue;
								Point point2 = new Point((int) num12, (int) num14);
								pathArray[j].AddLine(pointArray[j], point2);
								if (flag)
								{
									pathArray2[j].AddLine((int) (pointArray[j].X + base.shadow.OffsetX), (int) (pointArray[j].Y + base.shadow.OffsetY), (int) (point2.X + base.shadow.OffsetX), (int) (point2.Y + base.shadow.OffsetY));
								}
								pointArray[j] = point2;
							}
						}
					}
					if (base.dataLabels.visible)
					{
						this.RenderDataLabels(graphics);
					}
				}
				for (int k = stackedCount - 1; k >= 0; k--)
				{
					pathArray[k].AddLine(pointArray[k], new Point(pointArray[k].X, 0));
					pathArray[k].CloseAllFigures();
					if (flag)
					{
						pathArray2[k].AddLine(pointArray[k].X + base.shadow.OffsetX, pointArray[k].Y + base.shadow.OffsetY, pointArray[k].X + base.shadow.OffsetX, 0);
						pathArray2[k].CloseAllFigures();
						graphics.FillPath(brush, pathArray2[k]);
					}
					graphics.FillPath(brushArray[k], pathArray[k]);
					graphics.DrawPath(penArray[k], pathArray[k]);
					penArray[k].Dispose();
					brushArray[k].Dispose();
					pathArray[k].Dispose();
				}
			}
		}

		protected override void RenderDataLabels(Graphics graphics)
		{
			if (base.dataLabels.font == null)
			{
				base.dataLabels.font = ChartText.DefaultFont;
			}
			ChartEngine engine = base.Engine;
			int maxWidth = base.DataLabelMaxWidth;
			StringFormat format = new StringFormat();
			format.Alignment = StringAlignment.Center;
			format.LineAlignment = StringAlignment.Near;
			int stackedCount = this.GetStackedCount(engine.Charts);
			if (stackedCount != 0)
			{
				StackedAreaChart[] chartArray = new StackedAreaChart[stackedCount];
				Pen[] penArray = new Pen[stackedCount];
				Brush[] brushArray = new Brush[stackedCount];
				Brush[] brushArray2 = new Brush[stackedCount];
				int index = 0;
				foreach (Chart chart in engine.Charts)
				{
					chartArray[index] = chart as StackedAreaChart;
					if (chartArray[index] != null)
					{
						penArray[index] = chart.dataLabels.border.GetPen(graphics);
						brushArray[index] = chart.dataLabels.background.GetBrush(graphics);
						brushArray2[index] = new SolidBrush(chart.dataLabels.foreColor);
						index++;
						if (index >= stackedCount)
						{
							break;
						}
					}
				}
				float scaleX = engine.scaleX;
				float scaleY = engine.scaleY;
				for (int i = 0; i < engine.MaxPoints; i++)
				{
					float num6 = 0f;
					float num7 = 0f;
					for (int j = 0; j < stackedCount; j++)
					{
						ChartPointCollection data = chartArray[j].Data;
						if (data.Count > i)
						{
							RectangleF rectangle;
							ChartPoint point = data[i];
							float yvalue = point.yvalue;
							string dataLabelText = base.GetDataLabelText(point);
							if (yvalue > 0f)
							{
								num6 += yvalue;
								rectangle = base.GetDataLabelRectangle(graphics, num6, dataLabelText, maxWidth, i);
								base.DrawDataLabel(graphics, dataLabelText, rectangle, penArray[j], brushArray[j], format, brushArray2[j]);
							}
							else if (yvalue < 0f)
							{
								rectangle = base.GetDataLabelRectangle(graphics, num7, dataLabelText, maxWidth, i);
								num7 += yvalue;
								base.DrawDataLabel(graphics, dataLabelText, rectangle, penArray[j], brushArray[j], format, brushArray2[j]);
							}
						}
					}
				}
			}
		}
	}
}
